<template>
  <AutoComplete
    :id="documentId"
    v-model="data"
    icon="ios-search"
    @keydown.native="onKeydown"
    @on-select="onSelect"
    @on-change="onChange"
    @on-blur="onBlur"
    @on-focus.prevent.stop="onFocus"
    @on-clear="onClear"
    clearable
    :disabled="disabled"
    :placeholder="placeholder"
    transfer
    style="width:200px">
    <div class="cus-auto-body">
      <Option class="cus-auto-body-group"
              :disabled="disabledType != '' && option.typeSpecialty && option.typeSpecialty != disabledType"
              @click.native="onClick(option,index)"
              :class="[value[keyLabel] == option[keyLabel] ? 'ivu-select-item-selected ivu-select-item-focus' : '']"
              v-for="(option,index) in list" size="large"
              :value="option[keyLabel]" :key="index">
        <span class="cus-auto-body-group-title">{{ disabledType && option.typeSpecialty != disabledType ? `${option[keyLabel]}(${option.typeSpecialty})`: option[keyLabel]}}</span>
      </Option>
      <div style="position: relative">
        <Spin class="cus-auto-body-more" v-if="loading"></Spin> 
        <div class="cus-auto-body-more" @click.stop="isLoadMore=true;onMore()" v-if="!loading && !finished">查看更多</div>
        <div class="cus-auto-body-more" v-if="finished">没有更多啦~</div>
      </div>
    </div>
  </AutoComplete>
</template>

<script>
/**
   * 语法糖value
   * @fnc 接口列表方法
   * @fncLabel 接口参数字段名
   * @keyLabel select 展示字段
   * @keyValue select 选中字段
   * @cusParams cusParams 额外参数
   * @onChange 回调方法 -> 返回当前选中对象,索引(option,index)
   */
export default {
  name: 'cus-autoComplete',
  data () {
    return {
      data: '',
      loading: true,
      finished: false,
      pages: {
        page: 1,
        pageSize: 10
      },
      isLoadMore: false,
      tempList: [],
      list: []
    }
  },
  props: {
    value: {
      type: Object,
      default: () => {
        return {
          label: '',
          value: ''
        }
      }
    },
    fnc: {
      type: Function,
      default: () => {
        return () => {
        }
      }
    },
    disabled: {
      type: [Boolean],
      default: false
    },
    fncLabel: {
      type: [String],
      default: 'name'
    },
    pageSize: {
      type: [String, Number],
      default: 0
    },
    keyLabel: {
      type: [String, Number],
      default: 'label'
    },
    keyValue: {
      type: [String, Number],
      default: 'value'
    },
    cusParams: {
      type: Object,
      default: () => {
        return {}
      }
    },
    placeholder: {
      type: String,
      default: '请输入'
    },
    returnLabel: {
      type: String,
      default: 'data'
    },
    // 是否给到下表
    nowIndex: {
      type: [String, Number],
      default: ''
    },
    disabledType: {
      type: String,
      default: ''
    },
    documentId:{
      type: String,
      default: 'input' + Math.round(Math.random() * 100000000)
    },
    currentPage: {
      type: String,
      default: 'currentPage'
    },
    pageSize: {
      type: String,
      default: 'pageSize'
    },
  },
  watch: {
    value: {
      handler (val) {
        this.data = val[this.keyLabel]
      },
      immediate: true,
      deep: true
    }
  },
  mounted () {
    if (this.data && this.value[this.keyValue]){
        this.data = this.value[this.keyLabel]
    }
    document.addEventListener('click', (e) => {
      if(e.target != document.querySelector('#' + this.documentId)) {
        this.onBlur();
      }
      // console.log(e);
    })
  },
  beforeDestroy() {
    document.removeEventListener('click', (e) => {
      // console.log('移除监听--')
    })
  },
  methods: {
    onReset () {
      return new Promise(resolve => {
        this.list = []
        this.pages.page = 1
        this.pages.pageSize = 10
        this.loading = true
        this.finished = false
        resolve()
      })
    },
    onKeydown ({ keyCode }) {
      if (keyCode == 37 || keyCode == 38 || keyCode == 39 || keyCode == 40 || keyCode == 9 || keyCode == 20 || keyCode == 17 || keyCode == 91 || keyCode == 18 || keyCode == 93 || keyCode == 145 || keyCode == 19 || keyCode == 45 || keyCode == 36 || keyCode == 33 || keyCode == 144 || keyCode == 46 || keyCode == 35 || keyCode == 34) return

      this.$cu.debounce(() => {
        this.onReset().then(() => this.getOptionsList())
      })
    },
    onBlur () {
      setTimeout(() => {
        if(this.isLoadMore) return this.isLoadMore = false;
        if (this.data && this.value[this.keyValue]) this.data = this.value[this.keyLabel]
        if (!this.value[this.keyLabel] && !this.list.length && !this.list.filter(v => { v[this.keyValue] == this.value[this.keyValue] }).length) {
          this.list = this.tempList;
          this.data = ''
        }
      },100);
    },
    onClear () {
      console.log('清空');
      if (!this.value[this.keyLabel]) return
      this.$cu.simulationClick('body')
      this.$emit('update:value', Object.assign(this.value, {
        [this.keyLabel]: '',
        [this.keyValue]: ''
      }))
      if(this.nowIndex === '') {
          this.$emit('onClear')
      } else {
          this.$emit('onClear', this.nowIndex)
      }
      this.data = ''
      this.$nextTick(() => this.onReset().then(() => this.getOptionsList()))
    },
    onFocus () {
      this.onReset().then(() => this.getOptionsList())
      return
      // console.log(this.list.filter(v => v[this.keyLabel] === this.value[this.keyLabel]))
      // if (this.list.filter(v => v[this.keyLabel] === this.value[this.keyLabel]).length) return this.list = this.tempList;
      // if ((!this.value[this.keyLabel] && !this.list.length) ||
      //   (this.value[this.keyLabel] && !this.finished) ||
      //   (!this.value[this.keyLabel] && !this.value[this.keyValue] && !this.list.length)) {
      //   this.onReset().then(() => this.getOptionsList())
      // } else this.list = this.tempList
    },
    onSelect (value) {
      let option = this.list.find(v => {
        return v[this.keyLabel] == value
      })
      this.onClick(option)
    },
    onChange (value) {
      // console.log(value);
    },
    onClick (option, index) {
      if(this.disabledType && option.typeSpecialty != this.disabledType) {
        return
      }
      this.$emit('update:value', Object.assign(this.value, {
        [this.keyLabel]: option[this.keyLabel],
        [this.keyValue]: option[this.keyValue]
      }))
      if(this.nowIndex === '') {
          this.$emit('onChange', option, index)
      } else {
          this.$emit('onChange', option, index, this.nowIndex)
      }
      this.data = option[this.keyLabel]
      this.tempList = this.$cu.deepClone(this.list)
    },
    onMore () {
      // this.loading = true
      this.getOptionsList()
    },
    getOptionsList () {
      this.loading = true
      return new Promise(resolve => {
        let params = {
          [this.fncLabel]: this.data,
          [this.currentPage]: this.pages.page,
          [this.pageSize]: this.pages.pageSize
        }
        Object.assign(params, this.cusParams)
        this.fnc(params).then(res => {
          this.loading = false
          if (res.code === 1 || res.retCode == 2000) {
            this.pages.page += 1
            
            if(res[this.returnLabel].list) {
              this.list = this.list.concat(res[this.returnLabel].list)
            } else {
              this.list = this.list.concat(res[this.returnLabel])
            }
            
            if (!this.data) {
              this.tempList = this.list;
            }
            // if(this.pageSize) {
            //   this.pages.page = 1;
            //   this.finished = true
            // }
            if(res[this.returnLabel].list) {
              if (res[this.returnLabel].list.length < this.pages.pageSize) this.finished = true
            } else {
              if (res[this.returnLabel].length < this.pages.pageSize) this.finished = true
            }
            
            resolve()
          }
        })
      })
    }
  }
}
</script>

<style scoped lang="less">
  .cus-auto-body {
    max-height: 300px;
    overflow-y: scroll;

    &-group {
      font-size: 12px;
      padding: 8px 15px;
      border-bottom: 1px solid #F6F6F6;

      &-title {
      }

      &-count {
      }
    }

    &-more {
      color: #3399ff;
      text-align: center;
      font-size: 12px;
      height: 32px;
      padding-top: 5px;
      display: flex;
      align-items: center;
      justify-content: center;
      cursor: pointer;
    }

    &-more:hover {
      color: #5cadff;
    }
  }
  .disabledOption {
    cursor: not-allowed;
    pointer-events: none;
  }
</style>
